package com.db.server.data;

import com.db.data.Order;
import com.db.data.Price;
import com.db.protocol.tags.OrderSide;
import com.db.protocol.tags.OrderType;

public class ServerOrder implements Comparable<ServerOrder>, Order {
	
	private String clientID;

	public String getClientID() {
		return clientID;
	}
	
	private String orderID;

	@Override
	public String getOrderID() {
		return orderID;
	}
	
	private String ticketSymbol;

	@Override
	public String getTicketSymbol() {
		return ticketSymbol;
	}
	
	private Price price;

	@Override
	public Price getPrice() {
		return price;
	}
	
	private int quantity;

	@Override
	public int getQuantity() {
		return quantity;
	}
	
	private OrderSide side;

	@Override
	public OrderSide getSide() {
		return side;
	}

	private OrderType type;
	
	@Override
	public OrderType getType() {
		return type;
	}
	
	private int countOfNotFilled;
	
	public int getCountOfNotFilled() {
		return countOfNotFilled;
	}
	
	public void partiallyFilling(int quantity) {
		countOfNotFilled -= quantity;
	}
	
	public boolean filled() {
		return countOfNotFilled <= 0;
	}

	public ServerOrder(String clientID, String orderID, String ticketSymbol,
			Price price, int quantity, OrderSide side) {
		this.clientID = clientID;
		this.orderID = orderID;
		this.ticketSymbol = ticketSymbol;
		this.price = price;
		this.quantity = quantity;
		this.side = side;
		this.type = OrderType.LIMIT;
		this.countOfNotFilled = quantity;
	}
	
	public ServerOrder(String clientID, String orderID, String ticketSymbol,
			int quantity, OrderSide side) {
		super();
		this.clientID = clientID;
		this.orderID = orderID;
		this.ticketSymbol = ticketSymbol;
		this.price = new Price();
		this.quantity = quantity;
		this.side = side;
		this.type = OrderType.MARKET;
		this.countOfNotFilled = quantity;
	}

	@Override
	public int compareTo(ServerOrder otherOrder) {
		return price.compareTo(otherOrder.price);
	}

	@Override
	public int hashCode() {
		final int prime = 31;
		int result = 1;
		result = prime * result
				+ ((clientID == null) ? 0 : clientID.hashCode());
		result = prime * result + countOfNotFilled;
		result = prime * result + ((orderID == null) ? 0 : orderID.hashCode());
		result = prime * result + ((price == null) ? 0 : price.hashCode());
		result = prime * result + quantity;
		result = prime * result + ((side == null) ? 0 : side.hashCode());
		result = prime * result
				+ ((ticketSymbol == null) ? 0 : ticketSymbol.hashCode());
		result = prime * result + ((type == null) ? 0 : type.hashCode());
		return result;
	}

	@Override
	public boolean equals(Object obj) {
		if (this == obj)
			return true;
		if (obj == null)
			return false;
		if (getClass() != obj.getClass())
			return false;
		ServerOrder other = (ServerOrder) obj;
		if (clientID == null) {
			if (other.clientID != null)
				return false;
		} else if (!clientID.equals(other.clientID))
			return false;
		if (countOfNotFilled != other.countOfNotFilled)
			return false;
		if (orderID == null) {
			if (other.orderID != null)
				return false;
		} else if (!orderID.equals(other.orderID))
			return false;
		if (price == null) {
			if (other.price != null)
				return false;
		} else if (!price.equals(other.price))
			return false;
		if (quantity != other.quantity)
			return false;
		if (side != other.side)
			return false;
		if (ticketSymbol == null) {
			if (other.ticketSymbol != null)
				return false;
		} else if (!ticketSymbol.equals(other.ticketSymbol))
			return false;
		if (type != other.type)
			return false;
		return true;
	}
	
}
